<template>
  <div class="particle-container">
    <div class="info-panel">
      <h3>白色粒子系统</h3>
      <p>当前状态: {{ currentState }}</p>
      <p>粒子数量: {{ particleCount }}</p>
      <el-button @click="toggleAnimation" :type="isAnimating ? 'danger' : 'success'">
        {{ isAnimating ? '暂停' : '播放' }}
      </el-button>
    </div>
    <div ref="container" class="particle-canvas"></div>
  </div>
</template>

<script>
import * as THREE from 'three';
import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls';

export default {
  name: 'WhiteParticles',
  data() {
    return {
      isAnimating: true,
      particleCount: 1500,
      currentState: '自由漂浮',
      particles: [],
      particleGroup: null,
      shapeTimer: null,
      stateTimer: 0,
      isFormingShape: false,
      targetPositions: []
    };
  },
  mounted() {
    this.initThreeJS();
    window.addEventListener('resize', this.onWindowResize);
    this.startShapeCycle();
  },
  beforeDestroy() {
    window.removeEventListener('resize', this.onWindowResize);
    if (this.animationFrameId) {
      cancelAnimationFrame(this.animationFrameId);
    }
    if (this.shapeTimer) {
      clearInterval(this.shapeTimer);
    }
    if (this.renderer) {
      this.renderer.dispose();
    }
  },
  methods: {
    initThreeJS() {
      // 初始化场景 - 黑色背景
      this.scene = new THREE.Scene();
      this.scene.background = new THREE.Color(0x000000);

      // 初始化相机
      this.camera = new THREE.PerspectiveCamera(
        75,
        window.innerWidth / window.innerHeight,
        0.1,
        1000
      );
      this.camera.position.set(0, 0, 20);

      // 初始化渲染器
      this.renderer = new THREE.WebGLRenderer({ antialias: true });
      this.renderer.setSize(window.innerWidth, window.innerHeight);
      this.renderer.setPixelRatio(window.devicePixelRatio);
      this.$refs.container.appendChild(this.renderer.domElement);

      // 添加控制器
      this.controls = new OrbitControls(this.camera, this.renderer.domElement);
      this.controls.enableDamping = true;
      this.controls.dampingFactor = 0.05;

      // 添加环境光
      const ambientLight = new THREE.AmbientLight(0x404040, 0.6);
      this.scene.add(ambientLight);

      // 创建粒子组
      this.particleGroup = new THREE.Group();
      this.scene.add(this.particleGroup);

      // 创建白色粒子
      this.createParticles();

      // 开始渲染循环
      this.animate();
    },

    createParticles() {
      // 清空现有粒子
      this.particleGroup.clear();
      this.particles = [];
      this.targetPositions = [];

      const geometry = new THREE.SphereGeometry(0.05, 8, 8);
      const material = new THREE.MeshBasicMaterial({
        color: 0xffffff,
        transparent: true,
        opacity: 0.8
      });

      for (let i = 0; i < this.particleCount; i++) {
        const particle = new THREE.Mesh(geometry, material.clone());
        
        // 随机初始位置
        particle.position.set(
          (Math.random() - 0.5) * 15,
          (Math.random() - 0.5) * 15,
          (Math.random() - 0.5) * 15
        );

        this.particleGroup.add(particle);

        this.particles.push({
          mesh: particle,
          velocity: new THREE.Vector3(
            (Math.random() - 0.5) * 0.01,
            (Math.random() - 0.5) * 0.01,
            (Math.random() - 0.5) * 0.01
          ),
          originalPosition: particle.position.clone(),
          targetPosition: null,
          progress: 0
        });
      }
    },

    startShapeCycle() {
      this.shapeTimer = setInterval(() => {
        this.cycleShapes();
      }, 25000); // 25秒循环 (20秒自由 + 5秒形状)
    },

    cycleShapes() {
      this.stateTimer++;
      
      if (this.stateTimer % 2 === 1) {
        // 形成长方体
        this.formCuboid();
        this.currentState = '形成长方体';
        setTimeout(() => {
          this.releaseParticles();
          this.currentState = '自由漂浮';
        }, 5000);
      } else {
        // 形成正方体
        this.formCube();
        this.currentState = '形成正方体';
        setTimeout(() => {
          this.releaseParticles();
          this.currentState = '自由漂浮';
        }, 5000);
      }
    },

    formCuboid() {
      this.isFormingShape = true;
      const width = 8;
      const height = 4;
      const depth = 6;
      const spacing = 0.3;

      this.targetPositions = [];
      const particlesPerLayer = Math.floor(this.particleCount / 3);

      for (let i = 0; i < this.particleCount; i++) {
        let x, y, z;

        if (i < particlesPerLayer) {
          // 第一层 - 底部
          x = (i % Math.sqrt(particlesPerLayer) - Math.sqrt(particlesPerLayer)/2) * spacing;
          z = (Math.floor(i / Math.sqrt(particlesPerLayer)) - Math.sqrt(particlesPerLayer)/2) * spacing;
          y = -height/2;
        } else if (i < particlesPerLayer * 2) {
          // 第二层 - 中间
          const idx = i - particlesPerLayer;
          x = (idx % Math.sqrt(particlesPerLayer) - Math.sqrt(particlesPerLayer)/2) * spacing;
          y = (Math.floor(idx / Math.sqrt(particlesPerLayer)) - Math.sqrt(particlesPerLayer)/2) * spacing;
          z = 0;
        } else {
          // 第三层 - 顶部
          const idx = i - particlesPerLayer * 2;
          x = (idx % Math.sqrt(particlesPerLayer) - Math.sqrt(particlesPerLayer)/2) * spacing;
          z = (Math.floor(idx / Math.sqrt(particlesPerLayer)) - Math.sqrt(particlesPerLayer)/2) * spacing;
          y = height/2;
        }

        this.targetPositions.push(new THREE.Vector3(x, y, z));
        this.particles[i].targetPosition = this.targetPositions[i];
        this.particles[i].progress = 0;
      }
    },

    formCube() {
      this.isFormingShape = true;
      const size = 6;
      const spacing = 0.3;
      const sideLength = Math.cbrt(this.particleCount);

      this.targetPositions = [];

      for (let i = 0; i < this.particleCount; i++) {
        const x = (i % sideLength - sideLength/2) * spacing;
        const y = (Math.floor(i / sideLength) % sideLength - sideLength/2) * spacing;
        const z = (Math.floor(i / (sideLength * sideLength)) - sideLength/2) * spacing;

        this.targetPositions.push(new THREE.Vector3(x, y, z));
        this.particles[i].targetPosition = this.targetPositions[i];
        this.particles[i].progress = 0;
      }
    },

    releaseParticles() {
      this.isFormingShape = false;
      this.particles.forEach(particle => {
        particle.targetPosition = null;
        // 给粒子新的随机速度
        particle.velocity.set(
          (Math.random() - 0.5) * 0.01,
          (Math.random() - 0.5) * 0.01,
          (Math.random() - 0.5) * 0.01
        );
      });
    },

    animate() {
      this.animationFrameId = requestAnimationFrame(this.animate);

      if (this.isAnimating) {
        this.updateParticles();
      }

      this.controls.update();
      this.renderer.render(this.scene, this.camera);
    },

    updateParticles() {
      this.particles.forEach(particle => {
        if (this.isFormingShape && particle.targetPosition) {
          // 向目标位置移动
          particle.progress += 0.02;
          if (particle.progress > 1) particle.progress = 1;
          
          particle.mesh.position.lerpVectors(
            particle.mesh.position,
            particle.targetPosition,
            particle.progress
          );
        } else {
          // 自由漂浮
          particle.mesh.position.add(particle.velocity);

          // 边界检查 - 柔和反弹
          const position = particle.mesh.position;
          const bounds = 10;
          
          if (Math.abs(position.x) > bounds) particle.velocity.x *= -0.8;
          if (Math.abs(position.y) > bounds) particle.velocity.y *= -0.8;
          if (Math.abs(position.z) > bounds) particle.velocity.z *= -0.8;

          // 缓慢恢复到中心
          particle.velocity.x -= position.x * 0.0001;
          particle.velocity.y -= position.y * 0.0001;
          particle.velocity.z -= position.z * 0.0001;

          // 速度限制
          particle.velocity.clampLength(0, 0.03);
        }
      });
    },

    onWindowResize() {
      this.camera.aspect = window.innerWidth / window.innerHeight;
      this.camera.updateProjectionMatrix();
      this.renderer.setSize(window.innerWidth, window.innerHeight);
    },

    toggleAnimation() {
      this.isAnimating = !this.isAnimating;
    }
  }
};
</script>

<style scoped>
.particle-container {
  width: 100%;
  height: 100vh;
  margin: 0;
  padding: 0;
  overflow: hidden;
  position: relative;
  background: #000000;
}

.particle-canvas {
  width: 100%;
  height: 100%;
}

.info-panel {
  position: absolute;
  top: 20px;
  left: 20px;
  z-index: 1000;
  background: rgba(0, 0, 0, 0.7);
  color: white;
  padding: 15px;
  border-radius: 8px;
  backdrop-filter: blur(10px);
}

.info-panel h3 {
  margin: 0 0 10px 0;
  color: #ffffff;
}

.info-panel p {
  margin: 5px 0;
  font-size: 14px;
}

.info-panel .el-button {
  margin-top: 10px;
}
</style>
